#include "stdafx.h"
#include "LhsTreeNode.h"
#include "ComputationalTreeNodeVisitor.h"

using CollabRC::Bot::AI::ComputationalTreeNode;
using CollabRC::Bot::AI::LhsTreeNode;

/**
 * @brief creates a new LhsTreeNode from the specified branches
 * @param lhs the left hand branch which will be used in the computation
 * @param rhs the right hand branch which will be discarded
 */
LhsTreeNode::LhsTreeNode(const ComputationalTreeNode& lhs, const ComputationalTreeNode& rhs)
:OperationTreeNode(lhs, rhs),m_branch(&lhs)
{
}

/**
 * @brief creates a new LhsTreeNode from the existing operation
 * @param copy the operation from which to mutate to this LhsTreeNode
 */
LhsTreeNode::LhsTreeNode(const OperationTreeNode &copy)
:OperationTreeNode(copy),m_branch(NULL)
{
}

/** @brief Destroys this LhsTreeNode and all associated resources */
LhsTreeNode::~LhsTreeNode(void)
{
}

/** {@inheritDoc} */
float LhsTreeNode::PerformOperation(float lhs, float rhs) const
{
    rhs = rhs;      // To eliminate warnings for unused parameters
    return lhs;
}

/** {@inheritDoc} */
ComputationalTreeNode* LhsTreeNode::Clone() const
{
    if (m_branch)
        return m_branch->Clone();
    else
        return new LhsTreeNode(*this);
}

LhsTreeNode::Factory LhsTreeNode::factory;

/**
 * @brief Creates a new LhsTreeNode based off the specified
 * former operation
 *
 * Instead of creating a new LhsTreeNode directly, this function optimizes
 * out the redundant object by simply returning a clone of the left hand side.
 * @param copy the operation from which to copy the branches
 */
CollabRC::Bot::AI::ComputationalTreeNode* LhsTreeNode::Factory::Instantiate(const ComputationalTreeNode &lhs, const ComputationalTreeNode &rhs) const
{
    // Get rid of warnings for unused parameters - this should be optimized out
    const ComputationalTreeNode* v = &rhs;
    v = v;

    return lhs.Clone();
}

void LhsTreeNode::Accept(CollabRC::Bot::AI::ComputationalTreeNodeVisitor &visitor)
{
    OperationTreeNode::Accept(visitor);
    visitor.Visit(*this);
}
